package org.easy.alioss;

import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyun.oss.OSSException;
import com.aliyun.oss.model.OSSObject;
import com.aliyun.oss.model.PutObjectRequest;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.IOException;
import java.io.InputStream;
import java.time.LocalDateTime;
import java.time.ZoneId;
import java.util.Date;

public class AliOssAdapter {
    private static final Logger logger = LoggerFactory.getLogger(AliOssAdapter.class);


    public static OSS getOssClient(OssBaseProperties ossBaseProperties, String endpoint) {
        if (endpoint == null) {
            return new OSSClientBuilder().build(ossBaseProperties.getEndpoint(), ossBaseProperties.getAccessKeyId(), ossBaseProperties.getAccessKeySecret());
        } else {
            return new OSSClientBuilder().build(endpoint, ossBaseProperties.getAccessKeyId(), ossBaseProperties.getAccessKeySecret());
        }

    }


    public FileOutDto upload(OssBaseProperties ossBaseProperties, String endpoint, String bucket, String ossKey, InputStream inputStream) {
        OSS ossClient = getOssClient(ossBaseProperties, endpoint);
        try (InputStream uin = inputStream) {

            PutObjectRequest putObjectRequest = new PutObjectRequest(bucket, ossKey, uin);
            ossClient.putObject(putObjectRequest);

            FileOutDto fileOutDto = new FileOutDto();
            fileOutDto.setFilePath(getPublicUrl(ossBaseProperties.getProtocol(), endpoint, bucket, ossKey));
            fileOutDto.setBucket(bucket);
            fileOutDto.setEndpoint(endpoint);
            fileOutDto.setKey(ossKey);
            return fileOutDto;
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            ossClient.shutdown();
        }
        return null;
    }

    public String getPublicUrl(OssBaseProperties ossBaseProperties, String bucket, String ossKey) {
        return ossBaseProperties.getProtocol() + "://" + bucket + "." + ossBaseProperties.getEndpoint() + "/" + ossKey;
    }

    public String getPublicUrl(String protocol, String endpoint, String bucket, String ossKey) {
        return protocol + "://" + bucket + "." + endpoint + "/" + ossKey;
    }


    public String getPresignedUrl(OssBaseProperties ossBaseProperties, String endpoint, String bucket, String ossKey, Integer expires) {
        OSS ossClient = getOssClient(ossBaseProperties, endpoint);
        Date expiration = Date.from(LocalDateTime.now().plusSeconds(expires).atZone(ZoneId.systemDefault()).toInstant());
        return ossClient.generatePresignedUrl(bucket, ossKey, expiration).toString();
    }


    public Boolean isExitsObject(OssBaseProperties ossBaseProperties, String bucket, String ossKey) {
        OSS ossClient = getOssClient(ossBaseProperties, null);
        return ossClient.doesObjectExist(bucket, ossKey);
    }


    public InputStream downloadFile(OssBaseProperties ossBaseProperties, String bucket, String ossKey) {
        OSS ossClient = getOssClient(ossBaseProperties, null);
        try {
            OSSObject ossObject = ossClient.getObject(bucket, ossKey);
            return ossObject.getObjectContent();
        } catch (OSSException serviceException) {
            logger.error("serviceException", serviceException);
        }
        return null;
    }
}
